// utils/util.js
/**
 * 通用工具类
 * 提供各种通用的工具函数
 */

/**
 * 格式化数字，小于10的数字前面加0
 * @param {number} n - 需要格式化的数字
 * @returns {string} 格式化后的字符串
 */
const formatNumber = (n) => {
  const str = n.toString();
  return str.length >= 2 ? str : `0${str}`;
};

/**
 * 格式化时间
 * @param {Date|string|number} date - 日期对象或时间戳
 * @param {string} format - 格式化模式，默认 'YYYY/MM/DD HH:mm:ss'
 * @returns {string} 格式化后的时间字符串
 */
const formatTime = (date, format = 'YYYY/MM/DD HH:mm:ss') => {
  const d = new Date(date);
  
  if (isNaN(d.getTime())) {
    console.warn('无效的日期参数:', date);
    return '';
  }
  
  const year = d.getFullYear();
  const month = d.getMonth() + 1;
  const day = d.getDate();
  const hour = d.getHours();
  const minute = d.getMinutes();
  const second = d.getSeconds();

  const formatMap = {
    YYYY: year,
    MM: formatNumber(month),
    DD: formatNumber(day),
    HH: formatNumber(hour),
    mm: formatNumber(minute),
    ss: formatNumber(second)
  };

  return format.replace(/YYYY|MM|DD|HH|mm|ss/g, match => formatMap[match]);
};

/**
 * 获取相对时间表示（多久之前）
 * @param {Date|string|number} date - 日期对象或时间戳
 * @returns {string} 相对时间表示
 */
const getRelativeTime = (date) => {
  const now = new Date();
  const targetDate = new Date(date);
  const diff = now.getTime() - targetDate.getTime();
  
  if (diff < 0) {
    return '刚刚';
  }
  
  const minute = 60 * 1000;
  const hour = 60 * minute;
  const day = 24 * hour;
  const week = 7 * day;
  const month = 30 * day;
  const year = 365 * day;
  
  if (diff < minute) {
    return '刚刚';
  } else if (diff < hour) {
    return `${Math.floor(diff / minute)}分钟前`;
  } else if (diff < day) {
    return `${Math.floor(diff / hour)}小时前`;
  } else if (diff < week) {
    return `${Math.floor(diff / day)}天前`;
  } else if (diff < month) {
    return `${Math.floor(diff / week)}周前`;
  } else if (diff < year) {
    return `${Math.floor(diff / month)}个月前`;
  } else {
    return `${Math.floor(diff / year)}年前`;
  }
};

/**
 * 防抖函数
 * @param {Function} func - 需要防抖的函数
 * @param {number} delay - 延迟时间（毫秒）
 * @returns {Function} 防抖后的函数
 */
const debounce = (func, delay = 300) => {
  let timeoutId;
  return function (...args) {
    clearTimeout(timeoutId);
    timeoutId = setTimeout(() => func.apply(this, args), delay);
  };
};

/**
 * 节流函数
 * @param {Function} func - 需要节流的函数
 * @param {number} delay - 节流时间（毫秒）
 * @returns {Function} 节流后的函数
 */
const throttle = (func, delay = 300) => {
  let lastExecTime = 0;
  return function (...args) {
    const currentTime = Date.now();
    if (currentTime - lastExecTime >= delay) {
      func.apply(this, args);
      lastExecTime = currentTime;
    }
  };
};

/**
 * 深度克隆对象
 * @param {any} obj - 需要克隆的对象
 * @returns {any} 克隆后的对象
 */
const deepClone = (obj) => {
  if (obj === null || typeof obj !== 'object') {
    return obj;
  }
  
  if (obj instanceof Date) {
    return new Date(obj.getTime());
  }
  
  if (obj instanceof Array) {
    return obj.map(item => deepClone(item));
  }
  
  if (typeof obj === 'object') {
    const clonedObj = {};
    for (const key in obj) {
      if (obj.hasOwnProperty(key)) {
        clonedObj[key] = deepClone(obj[key]);
      }
    }
    return clonedObj;
  }
};

/**
 * 生成随机ID
 * @param {number} length - ID长度，默认8
 * @returns {string} 随机ID
 */
const generateId = (length = 8) => {
  const chars = 'ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789';
  let result = '';
  for (let i = 0; i < length; i++) {
    result += chars.charAt(Math.floor(Math.random() * chars.length));
  }
  return result;
};

/**
 * 数组去重
 * @param {Array} arr - 需要去重的数组
 * @param {string} key - 对象数组的唯一键名（可选）
 * @returns {Array} 去重后的数组
 */
const unique = (arr, key) => {
  if (!Array.isArray(arr)) {
    return [];
  }
  
  if (key) {
    const seen = new Set();
    return arr.filter(item => {
      const value = item[key];
      if (seen.has(value)) {
        return false;
      }
      seen.add(value);
      return true;
    });
  } else {
    return [...new Set(arr)];
  }
};

/**
 * 格式化文件大小
 * @param {number} bytes - 字节数
 * @param {number} decimals - 小数点位数，默认2
 * @returns {string} 格式化后的文件大小
 */
const formatFileSize = (bytes, decimals = 2) => {
  if (bytes === 0) return '0 Bytes';
  
  const k = 1024;
  const dm = decimals < 0 ? 0 : decimals;
  const sizes = ['Bytes', 'KB', 'MB', 'GB', 'TB'];
  
  const i = Math.floor(Math.log(bytes) / Math.log(k));
  
  return parseFloat((bytes / Math.pow(k, i)).toFixed(dm)) + ' ' + sizes[i];
};

/**
 * 验证邮箱格式
 * @param {string} email - 邮箱地址
 * @returns {boolean} 是否为有效邮箱
 */
const isValidEmail = (email) => {
  const emailRegex = /^[^\s@]+@[^\s@]+\.[^\s@]+$/;
  return emailRegex.test(email);
};

/**
 * 验证手机号格式（中国大陆）
 * @param {string} phone - 手机号
 * @returns {boolean} 是否为有效手机号
 */
const isValidPhone = (phone) => {
  const phoneRegex = /^1[3-9]\d{9}$/;
  return phoneRegex.test(phone);
};

module.exports = {
  formatTime,
  formatNumber,
  getRelativeTime,
  debounce,
  throttle,
  deepClone,
  generateId,
  unique,
  formatFileSize,
  isValidEmail,
  isValidPhone
};
